﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.IO;
using Syntezator_mowy.Extras.Exception;

namespace Merger.Wav
{
    class WavHeader
    {
        private byte[] chunkId;
        private byte[] chunkSize;
        private byte[] format;

        public int ChunkSize
        {
            set
            {
                if (value.GetType() == typeof(int))
                {
                    this.chunkSize = BitConverter.GetBytes(value);
                }
            }

        }

        public WavHeader() : this(0) { }

        public WavHeader(int chunkSize)
        {
            ASCIIEncoding encoder = new ASCIIEncoding();
            this.chunkId = new byte[4];
            this.chunkId = encoder.GetBytes("RIFF");

            this.chunkSize = new byte[4];
            this.chunkSize = BitConverter.GetBytes(chunkSize);

            this.format = new byte[4];
            this.format = encoder.GetBytes("WAVE");
        }

        public WavHeader(byte[] chunkId, byte[] chunkSize, byte[] format)
        {
            ASCIIEncoding encoder = new ASCIIEncoding();
            if (chunkId.Length != 4)
                throw new WrongFormatException();
            else if (encoder.GetString(chunkId) != "RIFF")
                throw new HeaderFormatException();
            else
                this.chunkId = chunkId;

            if (chunkSize.Length != 4)
                throw new WrongFormatException();
            else
                this.chunkSize = chunkSize;

            if (format.Length != 4)
                throw new WrongFormatException();
            else if (encoder.GetString(format) != "WAVE")
                throw new HeaderFormatException();
            else
                this.format = format;

        }

        public override bool Equals(object obj)
        {
            if (obj == null)
                return false;

            WavHeader header = obj as WavHeader;
            if (header == null)
                return false;

            return (this.chunkSize == header.chunkSize);
        }

        public bool Equals(WavHeader header)
        {
            if (header == null)
                return false;

            return (this.chunkSize == header.chunkSize);
        }

        public override int GetHashCode()
        {
            return this.chunkId.GetHashCode() ^ this.chunkSize.GetHashCode() ^ this.format.GetHashCode();
        }

        public static bool operator==(WavHeader a, WavHeader b)
        {
            if (Object.ReferenceEquals(a, b))
                return true;
            if ((a == null) || (b == null))
                return false;

            return (a.chunkSize == b.chunkSize);
        }

        public static bool operator !=(WavHeader a, WavHeader b)
        {
            return !(a == b);
        }

        public void saveHeader(string destinationPath)
        {
            using (BinaryWriter writer = new BinaryWriter(File.OpenWrite(destinationPath)))
            {
                writer.Seek(0, SeekOrigin.End);
                writer.Write(this.chunkId);
                writer.Write(this.chunkSize);
                writer.Write(this.format);
            }
        }

        public void changeHeaderSize(string destinationPath, int value)
        {
            using (BinaryWriter writer = new BinaryWriter(File.OpenWrite(destinationPath)))
            {
                writer.Seek(4, SeekOrigin.Begin);
                writer.Write(BitConverter.GetBytes(value));
                this.chunkSize = BitConverter.GetBytes(value);
            }
        }
    }
}
